package sxr.common.aspect;

import cn.thinkjoy.springboot.vuc.mg.mgdto.InterfaceCallLogDto;
import cn.thinkjoy.springboot.vuc.mg.mgservice.MongoDbService;
import com.alibaba.fastjson.JSONObject;
import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.annotation.*;
import org.aspectj.lang.reflect.MethodSignature;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;
import org.springframework.web.context.request.RequestContextHolder;
import org.springframework.web.context.request.ServletRequestAttributes;

import javax.servlet.http.HttpServletRequest;
import java.util.Arrays;

@Aspect
@Component
public class WebLogAspect {

    private static final Logger logger = LoggerFactory.getLogger(WebLogAspect.class);

    @Autowired
    private MongoDbService mongoDbService;

    @Pointcut("execution( * cn.thinkjoy.springboot..facade..*.*(..))&&!execution( * cn.thinkjoy.springboot.vuc.facade.impl.CommonFacadeImpl.*(..))")//两个..代表所有子目录，最后括号里的两个..代表所有参数
    public void webLogPointCut() {
    }

    @Around("webLogPointCut()")
    public Object doAround(ProceedingJoinPoint pjp) throws Throwable {
        long startTime = System.currentTimeMillis();
        Object ob = pjp.proceed();// ob 为方法的返回值
        logger.info("耗时 : " + (System.currentTimeMillis() - startTime));


        // 接收到请求，记录请求内容
        ServletRequestAttributes attributes = (ServletRequestAttributes) RequestContextHolder.getRequestAttributes();
        HttpServletRequest request = attributes.getRequest();

        // 记录下请求内容
        logger.info("请求地址 : " + request.getRequestURL().toString());
        logger.info("HTTP METHOD : " + request.getMethod());
        // 获取真实的ip地址
        //logger.info("IP : " + IPAddressUtil.getClientIpAddress(request));
        logger.info("CLASS_METHOD : " + pjp.getTarget().getClass().getName() + "." + pjp.getSignature().getName());
        MethodSignature signature = (MethodSignature) pjp.getSignature();
        logger.info("参数名："+ Arrays.toString(signature.getParameterNames()));
        logger.info("参数值: " + JSONObject.toJSONString(pjp.getArgs()));
        try{
            InterfaceCallLogDto interfaceCallLogDto= new InterfaceCallLogDto();

            //需要验证的参数位置
            int operIdLocation=-1;
            int appIdLocation=-1;
            //请求的参数名称
            String[] parameterNames = signature.getParameterNames();
            for (int i =0 ,len=parameterNames.length;i < len ;i++){
                if(parameterNames[i].equals("operId")){
                    operIdLocation=i;
                }
                if(parameterNames[i].equals("appId")){
                    appIdLocation=i;
                }
            }
            if(operIdLocation!=-1){
                interfaceCallLogDto.setOperId((String) pjp.getArgs()[operIdLocation]);
            }
            if(appIdLocation!=-1){
                interfaceCallLogDto.setSource((String) pjp.getArgs()[appIdLocation]);
            }
            interfaceCallLogDto.setRequsetURL(request.getRequestURL().toString());
            interfaceCallLogDto.setHttpMethod(request.getMethod());
            interfaceCallLogDto.setClassName(pjp.getTarget().getClass().getName());
            interfaceCallLogDto.setMethodName(pjp.getSignature().getName());
            interfaceCallLogDto.setParamsName(signature.getParameterNames());
            interfaceCallLogDto.setParams(pjp.getArgs());
            interfaceCallLogDto.setTakeUpTime(System.currentTimeMillis() - startTime);
            mongoDbService.saveInterfaceCallLogDto(interfaceCallLogDto);

        }catch (Exception e){
            e.printStackTrace();
        }

        return ob;
    }
}
